﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Security.Cryptography;
using System.Text;


public class CDataConvert
{
    static bool IS_HIGH_BEFOR = false;
    public static float FloatToFloat(float Data16, float SourceLowValue, float SourceHightValue, float DesLowValue, float DesHightValue)
    {
        float DataValue = Data16;
        if (DataValue > SourceHightValue) DataValue = SourceHightValue;
        if (DataValue < SourceLowValue) DataValue = SourceLowValue;

        float ret;
        ret = (((DataValue - SourceLowValue) / (SourceHightValue - SourceLowValue)) * (DesHightValue - DesLowValue)) + DesLowValue;
        return ret;
    }
    public static float UInt16ToFloat(UInt16 Data16, float SourceLowValue, float SourceHightValue, float DesLowValue, float DesHightValue)
    {
        float DataValue = Data16;
        if (DataValue > SourceHightValue) DataValue = SourceHightValue;
        if (DataValue < SourceLowValue) DataValue = SourceLowValue;

        float ret;
        ret = (((DataValue - SourceLowValue) / (SourceHightValue - SourceLowValue)) * (DesHightValue - DesLowValue)) + DesLowValue;
        return ret;
    }
    public static UInt16 Char2ToUInt16(byte cLow, byte cHigh)
    {
        UInt16 ret;
        if (IS_HIGH_BEFOR)
        {
            ret = (UInt16)((cHigh << 8) + cLow);
        }
        else
        {
            ret = (UInt16)((cLow << 8) + cHigh);
        }
        return ret;
    }
    public static void UInt16ToChar2(UInt16 data, out byte cLow, out byte cHigh)
    {
        if (IS_HIGH_BEFOR)
        {
            cHigh = (byte)(data >> 8);
            cLow = (byte)(data - ((data >> 8) << 8));
        }
        else
        {
            cLow = (byte)(data >> 8);
            cHigh = (byte)(data - ((data >> 8) << 8));
        }
    }

    public static UInt64 Char8ToUInt64(
        byte cLowLowLow, byte cLowLowHigh, byte cLowHighLow, byte cLowHighHigh,
        byte cHighLowLow, byte cHighLowHigh, byte cHighHighLow, byte cHighHighHigh
        )
    {
        UInt64 ret;
        UInt32 Low32, High32;
        Low32 = Char4ToUInt32(cLowLowLow, cLowLowHigh, cLowHighLow, cLowHighHigh);
        High32 = Char4ToUInt32(cHighLowLow, cHighLowHigh, cHighHighLow, cHighHighHigh);
        if (true == IS_HIGH_BEFOR)
        {
            UInt64 iTemp = High32;
            ret = ((UInt64)(iTemp << 32)) + Low32;
        }
        else
        {
            UInt64 iTemp = Low32;
            ret = (Low32 << 32) + High32;

        }
        return ret;

    }
    public static UInt32 Char4ToUInt32(byte cLowLow, byte cLowHigh, byte cHighLow, byte cHighHigh)
    {
        UInt32 ret;
        if (true == IS_HIGH_BEFOR)
        {
            ret = (UInt32)((((cHighHigh << 8) + cHighLow) << 16) + ((cLowHigh << 8) + cLowLow));
        }
        else
        {
            ret = (UInt32)((((cLowLow << 8) + cLowHigh) << 16) + ((cHighLow << 8) + cHighHigh));
        }
        return ret;
    }
    public static void UInt32ToChar4(UInt32 data, out byte cLowLow, out byte cLowHigh, out byte cHighLow, out byte cHighHigh)
    {
        UInt16 dataH16, dataL16;
        if (true == IS_HIGH_BEFOR)
        {
            dataH16 = (UInt16)(data >> 16);
            dataL16 = (UInt16)(data - (dataH16 << 16));

            cHighHigh = (byte)(dataH16 >> 8);
            cHighLow = (byte)(dataH16 - ((dataH16 >> 8) << 8));

            cLowHigh = (byte)(dataL16 >> 8);
            cLowLow = (byte)(dataL16 - ((dataL16 >> 8) << 8));
        }
        else
        {
            dataH16 = (UInt16)(data >> 16);
            dataL16 = (UInt16)(data - (dataH16 << 16));

            cLowLow = (byte)(dataH16 >> 24);
            cLowHigh = (byte)(dataH16 - ((dataH16 >> 8) << 8));

            cHighLow = (byte)(dataL16 >> 8);
            cHighHigh = (byte)(dataL16 - ((dataL16 >> 8) << 8));
        }

    }

    public static UInt64 GetValue(ref byte[] bSendData, int iFrom, int iLength)
    {
        UInt64 ret = 0;
        System.Diagnostics.Debug.Assert(iFrom >= 0 && iFrom + iLength <= bSendData.Length && iLength > 0);
        if (iLength == 1)
        {
            ret = bSendData[iFrom];
        }
        else if (iLength == 2)
        {
            ret = CDataConvert.Char2ToUInt16(bSendData[iFrom], bSendData[iFrom + 1]);
        }
        else if (iLength == 4)
        {
            ret = CDataConvert.Char4ToUInt32(bSendData[iFrom], bSendData[iFrom + 1], bSendData[iFrom + 2], bSendData[iFrom + 3]);
        }
        else if (iLength == 8)
        {
            ret = CDataConvert.Char8ToUInt64(
                bSendData[iFrom + 0], bSendData[iFrom + 1], bSendData[iFrom + 2], bSendData[iFrom + 3],
                bSendData[iFrom + 4], bSendData[iFrom + 5], bSendData[iFrom + 6], bSendData[iFrom + 7]
                );
        }
        return ret;
    }
    public static void SetValue(uint iValue, ref byte[] bSendData, int iFrom, int iLength)
    {
        System.Diagnostics.Debug.Assert(iFrom >= 0 && iFrom + iLength <= bSendData.Length && iLength > 0);
        if (iLength == 1)
        {

            bSendData[iFrom] = (byte)iValue;
        }
        else if (iLength == 2)
        {
            CDataConvert.UInt16ToChar2((UInt16)iValue, out bSendData[iFrom], out bSendData[iFrom + 1]);
        }
        else if (iLength == 4)
        {
            CDataConvert.UInt32ToChar4((UInt32)iValue, out bSendData[iFrom], out bSendData[iFrom + 1], out bSendData[iFrom + 2], out bSendData[iFrom + 3]);
        }
    }
    public static void IPByteStringToIP(byte[] bIP, int iFrom, int iLength, out string IP)
    {
        int i;
        IP = "";
        System.Diagnostics.Debug.Assert(iLength == 4);
        for (i = 0; i < 4; ++i)
        {
            IP += System.Convert.ToString(bIP[i + iFrom]);
            if (i != 3) IP += ".";
        }

    }
    public static void IPStringToIPByte(string IP, out byte[] bIP)
    {
        bIP = new byte[4];
        int i;
        string[] splitIP = IP.Split(new Char[] { '.' });
        for (i = 0; i < 4; ++i)
        {
            bIP[i] = System.Convert.ToByte(splitIP[i]);
        }
    }
    public static UInt32 VBoolToUInt(List<bool> vData)
    {
        int i;
        UInt32 ret = 0;
        for (i = 0; i < vData.Count; ++i)
        {
            int isOpen = vData[i] == true ? 1 : 0;
            ret = (UInt32)(ret | (UInt32)(isOpen << i));
        }
        return ret;
    }
    public static List<bool> UIntToVBool(UInt32 uData)
    {
        int i;
        List<bool> vData = new List<bool>();
        for (i = 0; i < sizeof(UInt32) * 8; ++i)
        {
            bool isOpen = ((uData & (1 << i)) == (1 << i)) ? true : false;
            vData.Add(isOpen);
        }
        return vData;
    }
    public static List<bool> UInt16ToVBool(UInt16 uData)
    {
        int i;
        List<bool> vData = new List<bool>();
        for (i = 0; i < sizeof(UInt16) * 8; ++i)
        {
            bool isOpen = ((uData & (1 << i)) == (1 << i)) ? true : false;
            vData.Add(isOpen);
        }
        return vData;
    }
    public static float[] ByteArrayToFloatArray(byte[] bData)
    {
        int i;
        System.Diagnostics.Debug.Assert(bData.Length % sizeof(float) == 0);
        float[] ret = new float[bData.Length / sizeof(float)];
        for (i = 0; i < ret.Length; ++i)
        {
            ret[i] = BitConverter.ToSingle(bData, i * sizeof(float));
        }
        return ret;
    }
    public static byte[] FloatArrayToByteArray(float[] bData)
    {
        int i;
        byte[] ret = null;
        if (bData != null)
        {

            ret = new byte[bData.Length * sizeof(float)];
            for (i = 0; i < bData.Length; ++i)
            {
                BitConverter.GetBytes(bData[i]).CopyTo(ret, i * sizeof(float));
            }
        }
        return ret;
    }

    public static int[] ByteArrayToIntArray(byte[] bData)
    {
        int i;
        System.Diagnostics.Debug.Assert(bData.Length % sizeof(int) == 0);
        int[] ret = new int[bData.Length / sizeof(int)];
        for (i = 0; i < ret.Length; ++i)
        {
            ret[i] = BitConverter.ToInt32(bData, i * sizeof(int));
        }
        return ret;
    }
    public static byte[] IntArrayToByteArray(int[] bData)
    {
        int i;
        byte[] ret = null;
        if (bData != null)
        {

            ret = new byte[bData.Length * sizeof(int)];
            for (i = 0; i < bData.Length; ++i)
            {
                BitConverter.GetBytes(bData[i]).CopyTo(ret, i * sizeof(int));
            }
        }
        return ret;
    }
    public static string ByteToString(byte[] bSendData, int iFrom, int iLength)
    {
        string ret = System.Text.Encoding.Default.GetString(bSendData, iFrom, iLength);
        ret = ret.Trim('\0');
        return ret;
    }
    public static Int64 DateTimeToInt64(DateTime dateTime)
    {
        Int64 ret = -1;
        DateTime BeginTime = new DateTime(2012, 1, 1, 0, 0, 0);
        ret = (Int64)((dateTime - BeginTime).TotalMilliseconds);
        return ret;
    }
    public static DateTime Int64ToDateTime(Int64 iTime)
    {
        DateTime ret;
        DateTime BeginTime = new DateTime(2012, 1, 1, 0, 0, 0);
        ret = BeginTime.AddMilliseconds(iTime);
        return ret;
    }
    public static string ToSha1String(string str)
    {

        byte[] StrRes = Encoding.Default.GetBytes(str);
        HashAlgorithm iSHA = new SHA1CryptoServiceProvider();
        StrRes = iSHA.ComputeHash(StrRes);
        StringBuilder EnText = new StringBuilder();
        foreach (byte iByte in StrRes)
        {
            EnText.AppendFormat("{0:x2}", iByte);
        }
        string ret = EnText.ToString();
        return ret;

        //Guid GStart = Guid.Empty;
        //return GStart.Parse(str);
    }
    public static byte[] WithCode(byte[] iData)
    {
        byte[] ret = null;
        string sCode = "zhaoming";
        byte[] buffer = System.Text.Encoding.Default.GetBytes(sCode);

        if (iData.Length > 0)
        {
            ret = new byte[iData.Length];
            int bTemp;
            int i, j = 0;
            for (i = 0; i < iData.Length; ++i)
            {
                bTemp = iData[i] + 68;
                // bTemp = iData[i] + buffer[j % buffer.Length];
                // bTemp = bTemp % 256;
                //if (bTemp > 255) bTemp -= 256;
                //if (bTemp < 0) bTemp += 256;
                ret[i] = (byte)bTemp;
                ++j;
            }
        }
        return ret;
    }
}